"""Controller for the DynamicConfigManager process."""

from google.protobuf import any_pb2
from test.integration import subprocess_mixin
from rules_python.python.runfiles import runfiles
import base64
import os
from os import path
import time
import logging


class DynamicConfigController(subprocess_mixin.SubprocessMixin):
  """Controller for the Dynamic Configuration Manager.

  Manages the subprocess used to generate Dynamic Configuration.
  See subprocess_mixin.SubprocessMixin for usage.
  """

  def __init__(self, dynamic_config_settings):
    """Create DynamicConfigController."""
    super().__init__()
    runfiles_instance = runfiles.Create()
    self._binary_path = runfiles_instance.Rlocation(
        'nighthawk/dynamic_config/dynamic_config_manager')
    self._settings = dynamic_config_settings

  def _argsForSubprocess(self) -> list[str]:
    wrapped_proto = any_pb2.Any()
    wrapped_proto.Pack(self._settings)
    serialized_wrapped_proto = wrapped_proto.SerializeToString()
    return [self._binary_path, '--config', str(base64.b64encode(serialized_wrapped_proto), 'UTF-8')]

  def start(self):
    """Start the DynamicConfigManager process.

    Returns:
        Bool: whether the process has started.
    """
    if path.exists(self._settings.output_file):
      os.remove(self._settings.output_file)
    logging.info(f"Launching subprocess with args {self._argsForSubprocess()}")
    self.launchSubprocess()
    time.sleep(self._settings.refresh_interval.ToSeconds() + 10)
    logging.info("Checking configuration file exists.")
    assert path.exists(self._settings.output_file), \
        f"Expected configuration file f{self._settings.output_file} to have been generated by the child process."
    return True

  def stop(self):
    """Stop the DynamicConfigManager process.

    Returns:
        Int: exit code of the server process.
    """
    return self.stopSubprocess()
